package com.neasho.neashoadminv1.web.service.sys

import com.neasho.neashoadminv1.infrastructure.domain.dto.sys.SysUserTokenInput
import com.neasho.neashoadminv1.infrastructure.domain.dto.sys.SysUserTokenQuery
import com.neasho.neashoadminv1.infrastructure.domain.sys.SysUser
import com.neasho.neashoadminv1.infrastructure.domain.sys.SysUserToken
import com.neasho.neashoadminv1.infrastructure.domain.sys.copy
import com.neasho.neashoadminv1.infrastructure.domain.sys.user
import com.neasho.neashoadminv1.infrastructure.exception.BusinessCode
import com.neasho.neashoadminv1.infrastructure.utils.ulid
import org.babyfish.jimmer.sql.kt.KSqlClient
import org.springframework.stereotype.Service
import java.time.LocalDateTime

@Service
class SysUserTokenService(
    val sqlClient: KSqlClient
) {

    /**
     * 申请一个新token
     */
    fun applyToken(userId: Long): SysUserToken {
        val now = LocalDateTime.now()
        val expireAt = now.plusMinutes(1)
        SysUserTokenInput(
            createAt = now,
            lastModifyAt = now,
            userId = userId,
            token = ulid(),
            expireAt = expireAt
        ).let {
            val entity = it.toEntity()
            if (sqlClient.save(entity).isRowAffected) {
                return entity
            }
            throw BusinessCode.user_login_failed.exception()
        }
    }

    /**
     * 根据token获取用户信息
     */
    fun getUserByToken(token: String): SysUser {
        val now = LocalDateTime.now()
        SysUserTokenQuery(
            token = token,
            currentTime = now
        ).let {
            val user = sqlClient.executeQuery(SysUserToken::class) {
                where(it)
                select(table.user)
            }.firstOrNull()
            return user ?: throw BusinessCode.user_credetial_expired.exception()
        }
    }

}